`include "C:\Users\lenovo\Desktop\Files\Linear_RISCV\LR_ver_0\src\include\include.vh"
module 	translater(
    input  [6:0]  opcode,
    input  [6:0]  funct7,
    input  [2:0]  funct3,	
    output reg [3:0]  exe_type,
    output reg [5:0]  uop_code
);
    
// exe_type generate
always @(*) begin
    case (opcode)
        `INST_RV32I_OPCODE_LUI: 
            exe_type = `EXE_TYPE_LUI;
        `INST_RV32I_OPCODE_AUIPC:
            exe_type = `EXE_TYPE_AUIPC;
        `INST_RV32I_OPCODE_JAL:
            exe_type = `EXE_TYPE_JAL;
        `INST_RV32I_OPCODE_JALR:
            exe_type = `EXE_TYPE_JALR;
        `INST_RV32I_OPCODE_BRANCH:
            exe_type = `EXE_TYPE_BRANCH;
        `INST_RV32DI_OPCODE_LOAD:
            exe_type = `EXE_TYPE_LOAD;
        `INST_RV32DI_OPCODE_STORE:
            exe_type = `EXE_TYPE_STORE;
        `INST_RV32I_OPCODE_IMM:
            exe_type = `EXE_TYPE_COMMON;
        `INST_RV32I_OPCODE_REG:    
            exe_type = `EXE_TYPE_COMMON;
        `INST_RV64I_OPCODE_SHIFT_W:
            exe_type = `EXE_TYPE_COMMON;
        `INST_RV64IM_OPCODE_REG:
            begin
                if(funct7 != 7'b0000001)begin
                    exe_type = `EXE_TYPE_COMMON;
                end
                else begin
                    case(funct3)
                        `INST_RV64M_MULW:
                            exe_type = `EXE_TYPE_MUL;
                        `INST_RV64M_DIVW:
                            exe_type = `EXE_TYPE_DIV;
                        `INST_RV64M_DIVUW:
                            exe_type = `EXE_TYPE_DIV;
                        `INST_RV64M_REMW:
                            exe_type = `EXE_TYPE_DIV;
                        `INST_RV64M_REMUW:
                            exe_type = `EXE_TYPE_DIV;    
                        default:
                            exe_type = `EXE_TYPE_NOP;                        
                    endcase
                end               

            end            
        `INST_RV32M_OPCODE_REG:
            begin
                case (funct3)
                    `INST_RV32M_MUL:
                        exe_type = `EXE_TYPE_MUL;
                    `INST_RV32M_MULH:
                        exe_type = `EXE_TYPE_MUL;
                    `INST_RV32M_MULHSU:
                        exe_type = `EXE_TYPE_MUL;
                    `INST_RV32M_MULHU:
                        exe_type = `EXE_TYPE_MUL;
                    `INST_RV32M_DIV:
                        exe_type = `EXE_TYPE_DIV;
                    `INST_RV32M_DIVU:
                        exe_type = `EXE_TYPE_DIV; 
                    default:
                        exe_type = `EXE_TYPE_NOP; 
                endcase                
            end
        default: 
            exe_type = `EXE_TYPE_NOP;
    endcase
end    

always@(*)begin
    case(opcode)
        `INST_RV32I_OPCODE_LUI:
            uop_code = `UOP_CODE_LUI;
        `INST_RV32I_OPCODE_AUIPC:
            uop_code = `UOP_CODE_AUIPC;
        `INST_RV32I_OPCODE_JAL:
            uop_code = `UOP_CODE_JAL;
        `INST_RV32I_OPCODE_JALR:
            uop_code = `UOP_CODE_JALR;
        `INST_RV32DI_OPCODE_LOAD:
            begin
                case(funct3)
                    `INST_RV32I_LB:
                        uop_code = `UOP_CODE_LB;
                    `INST_RV32I_LBU:
                        uop_code = `UOP_CODE_LBU;
                    `INST_RV32I_LH:
                        uop_code = `UOP_CODE_LH;
                    `INST_RV32I_LHU:
                        uop_code = `UOP_CODE_LHU;
                    `INST_RV32I_LW:
                        uop_code = `UOP_CODE_LW;
                    `INST_RV32I_LWU:
                        uop_code = `UOP_CODE_LWU;
                    `INST_RV32I_LD:
                        uop_code = `UOP_CODE_LD;
                    default:
                        uop_code = `UOP_CODE_NOP;    
                endcase
            end
        `INST_RV32DI_OPCODE_STORE:
            begin
                case(funct3)
                    `INST_RV32I_SB:
                        uop_code = `UOP_CODE_SB;
                    `INST_RV32I_SH:
                        uop_code = `UOP_CODE_SH;
                    `INST_RV32I_SW:
                        uop_code = `UOP_CODE_SW;
                    `INST_RV32I_SD:
                        uop_code = `UOP_CODE_SD;
                    default:
                        uop_code = `UOP_CODE_NOP;
                endcase
            end
        `INST_RV32I_OPCODE_IMM:
            begin
                case(funct3)
                    `INST_RV32I_ADDI:
                        uop_code = `UOP_CODE_ADDI;
                    `INST_RV32I_ANDI:
                        uop_code = `UOP_CODE_ANDI;
                    `INST_RV32I_SLTI:
                        uop_code = `UOP_CODE_SLTI;
                    `INST_RV32I_SLTIU:
                        uop_code = `UOP_CODE_SLTIU;
                    `INST_RV32I_SLLI:
                        uop_code = `UOP_CODE_SLLI;
                    `INST_RV32I_SRLI_SRAI:
                        uop_code = funct7[5]
                                  ?`UOP_CODE_SRLI
                                  :`UOP_CODE_SRAI;
                    `INST_RV32I_ORI:
                        uop_code = `UOP_CODE_ORI;
                    `INST_RV32I_XORI:
                        uop_code = `UOP_CODE_XORI;
                    default:
                        uop_code = `UOP_CODE_NOP;
                endcase
            end
        `INST_RV32I_OPCODE_BRANCH:
            begin
                case(funct3)
                    `INST_RV32I_BEQ:
                        uop_code = `UOP_CODE_BEQ;
                    `INST_RV32I_BNE:
                        uop_code = `UOP_CODE_BNE;
                    `INST_RV32I_BLT:
                        uop_code = `UOP_CODE_BLT;
                    `INST_RV32I_BGE:
                        uop_code = `UOP_CODE_BGE;
                    `INST_RV32I_BLTU:
                        uop_code = `UOP_CODE_BLTU;
                    `INST_RV32I_BGEU:
                        uop_code = `UOP_CODE_BGEU;
                    default:
                        uop_code = `UOP_CODE_NOP;
                endcase
            end
        `INST_RV32I_OPCODE_REG:
            begin
                case(funct3)
                    `INST_RV32I_ADD_SUB:
                        uop_code = funct7[5]?
                                  `UOP_CODE_SUB:
                                  `UOP_CODE_ADD;
                    `INST_RV32I_AND:
                        uop_code = `UOP_CODE_AND;
                    `INST_RV32I_SLT:
                        uop_code = `UOP_CODE_SLT;
                    `INST_RV32I_SLTU:
                        uop_code = `UOP_CODE_SLTU;
                    `INST_RV32I_SLL:
                        uop_code = `UOP_CODE_SLL;
                    `INST_RV32I_SRL_SRA:
                        uop_code = funct7[5]
                                  ?`UOP_CODE_SRA
                                  :`UOP_CODE_SRL;
                    `INST_RV32I_OR:
                        uop_code = `UOP_CODE_OR;
                    `INST_RV32I_XOR:
                        uop_code = `UOP_CODE_XOR;                   
                    default:
                        uop_code = `UOP_CODE_NOP;
                endcase
            end
        `INST_RV32M_OPCODE_REG:
            begin
                case(funct3)
                    `INST_RV32M_MUL:
                        uop_code = `UOP_CODE_MUL;
                    `INST_RV32M_MULH:
                        uop_code = `UOP_CODE_MULH;
                    `INST_RV32M_MULHSU:
                        uop_code = `UOP_CODE_MULHSU;
                    `INST_RV32M_MULHU:
                        uop_code = `UOP_CODE_MULHU;
                    `INST_RV32M_DIV:
                        uop_code = `UOP_CODE_DIV;
                    `INST_RV32M_DIVU:
                        uop_code = `UOP_CODE_DIVU;
                    `INST_RV32M_REM:
                        uop_code = `UOP_CODE_REM;
                    `INST_RV32M_REMU:
                        uop_code = `UOP_CODE_REMU;
                    default:
                        uop_code = `UOP_CODE_NOP;
                endcase
            end
        `INST_RV64IM_OPCODE_REG:
            begin
                if (funct7 == 7'b0000001) begin//RV64M
                    case(funct3)
                        `INST_RV64M_MULW:
                            uop_code = `UOP_CODE_MULW;
                        `INST_RV64M_DIVW:
                            uop_code = `UOP_CODE_DIVW;
                        `INST_RV64M_DIVUW:
                            uop_code = `UOP_CODE_DIVUW;
                        `INST_RV64M_REMW:
                            uop_code = `UOP_CODE_REMW;
                        `INST_RV64M_REMUW:
                            uop_code = `UOP_CODE_REMUW;
                        default:
                            uop_code = `UOP_CODE_NOP;
                    endcase 
                end else begin//RV64R
                    case(funct3)
                        `INST_RV32I_ADD_SUB:
                            uop_code = funct7[5]?
                                    `UOP_CODE_SUBW:
                                    `UOP_CODE_ADDW;
                        `INST_RV64I_SLLW:
                            uop_code = `UOP_CODE_SLLW;
                        `INST_RV64I_SRLW_SRAW:
                            uop_code = funct7[5]
                                    ?`UOP_CODE_SRAW
                                    :`UOP_CODE_SRLW;
                        `INST_RV32I_ADDI:
                            uop_code = `UOP_CODE_ADDIW;
                        default:
                            uop_code = `UOP_CODE_NOP;
                    endcase                    
                end                
            end
        `INST_RV64I_OPCODE_SHIFT_W:
            begin
                case(funct3)
                    `INST_RV64I_SLLIW:
                        uop_code = `UOP_CODE_SLLWI;
                    `INST_RV64I_SRLIW_SRAIW:
                        uop_code = funct7[5]
                                 ?`UOP_CODE_SRLWI
                                 :`UOP_CODE_SRAWI;
                    default:
                        uop_code = `UOP_CODE_NOP;
                endcase
            end
        default:
            uop_code = `UOP_CODE_NOP;
    endcase
end



endmodule